""" 

    cache.py used in RepresentedBy Facebook application
    http://apps.facebook.com/representedby/
    
    This script is not ever used in the application but rather is called by
    a cron job running on a separate web server.  It's meant to be pinged once every minute.
    It's purpose is to prepopulate the memcache of the system with the contents of the various APIs.

    I did the math, and the core functionality of the site involves around 3,000 different API calls, and one
    page alone can require up to 50 different API calls.  No one wants to sit and wait for all this, so every
    minute I'm randomly picking a handful of API calls to make and store in the cache.  This helps keep the
    memcache fresh, and reduce the amount of actual pings we have to do to outside URLs when users try
    and render a page.
    
    This has been the saving grace for me in terms of site performance. 
        
"""

__author__ = "Will Turnage (will @t wubbahed d0t com)"
__version__ = "0.1.0"
__copyright__ = "Copyright (c) 2009 wubbahed.com"
__license__ = "GPLv3"

import os
import wsgiref.handlers
import const
import random

from django.utils import simplejson
from google.appengine.ext import webapp
from google.appengine.ext.webapp import template
from google.appengine.ext.webapp.util import run_wsgi_app
from google.appengine.api import memcache
from google.appengine.api import urlfetch
        
from utils import fbUtil, dbUtil, UserDistrict, SunlightUtil, NYTimesUtil, memcacheUtil

class MainHandler(webapp.RequestHandler):

    def post(self):
        self.get()
        
    def get(self):
        
        if self.request.get('clear') == "all":
            memcache.flush_all()
        elif self.request.get('stats') == "all":
            self.response.out.write(str(memcache.get_stats()))
        else:
            hits = 3
            repCount = len(const.REPRESENTATIVES)
            stateCount = len(const.LEGISLATORS_BY_STATE)
            senCount = len(const.SENATORS)
            totalCount = repCount + senCount
            max = repCount + stateCount + (totalCount*2)
            sunlight = SunlightUtil(const.SUNLIGHT_API_KEY)
            nytimes = NYTimesUtil(const.NYTIMES_API_KEY)
            
            for i in range(hits):
                pick = random.randint(0, max-1)
                if (pick<repCount):
                    # set cache for getDistrictReps
                    for j in const.LEGISLATORS_BY_STATE:
                        repcount = len(const.LEGISLATORS_BY_STATE[j]['representatives'])
                        if pick < repcount:
                            if repcount == 1:
                                result = sunlight.apicall('legislators.getList', {"state": j, "district": str(pick)})
                            else:
                                result = sunlight.apicall('legislators.getList', {"state": j, "district": str(pick+1)})
                        else:
                            pick = pick - repcount
                else:
                    pick=pick-repCount
                    if (pick<stateCount):
                        # set cache for getSenators
                        states = const.LEGISLATORS_BY_STATE.keys()
                        result = sunlight.apicall('legislators.getList', {"title": "Sen", "state":states[pick]})
                    else:
                        pick = pick - stateCount
                        if (pick<totalCount):
                            #set cache for getSingleRep
                            if (pick < repCount):
                                result = sunlight.apicall('legislators.get', {"bioguide_id": const.REPRESENTATIVES[pick]})
                            else:
                                result = sunlight.apicall('legislators.get', {"bioguide_id": const.SENATORS[pick-repCount]})
                        else:
                            pick = pick - totalCount
                            if (pick<totalCount):
                                
                                #set cache for voting results
                                result = None
                                if (pick < repCount):
                                    result = nytimes.apicall(const.REPRESENTATIVES[pick])
                                else:
                                    result = nytimes.apicall(const.SENATORS[pick-repCount])
                                
                                #self.response.out.write(result)
                                #self.response.out.write("\n\n---\n\n")
                                if result is not None:
                                #    self.response.out.write("Bad result\n\n")
                                    ref = result[0]["votes"]
                                    hits = 0
                                    maxrange = 10
                                    if len(ref) < maxrange:
                                        maxrange = len(ref)
                                    for j in range(maxrange):    
                                        if (hits<3):
                                            url = const.NYTIMES_BASE_URL + "/" + str(ref[j]["congress"]) + "/" + str(ref[j]["chamber"]) + "/sessions/" + str(ref[j]["session"]) + "/votes/" + str(ref[j]["roll_call"]) + ".json?api-key=" + const.NYTIMES_API_KEY
                                            memcacheUtil().getJSONFromCache(url, "results")

        
def main():
    application = webapp.WSGIApplication([('/cache', MainHandler)],
                                       debug=True)
    run_wsgi_app(application)
                                       

if __name__ == '__main__':
    main()
